package com.xhwl.logistics.component;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.crypto.SecureUtil;
import cn.hutool.crypto.digest.DigestAlgorithm;
import com.alibaba.fastjson.JSON;
import com.xhwl.logistics.bo.cent.VehicleParkingInfoBO;
import com.xhwl.logistics.dto.http.manipulation.ManipulationKeTopCommonDTO;
import com.xhwl.logistics.dto.http.query.QueryCommonKeTopDTO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;
import org.springframework.util.DigestUtils;

import java.nio.charset.StandardCharsets;
import java.util.Map;
import java.util.TreeMap;
import java.util.UUID;

@Slf4j
@Component
public class Sign {

    public <T extends QueryCommonKeTopDTO> T preHandle(T t, String appId, Integer parkId, String serviceCode) {
        t.setAppId(appId);
        t.setParkId(parkId);
        t.setReqId(UUID.randomUUID().toString());
        t.setTs(String.valueOf(System.currentTimeMillis()));
        t.setServiceCode(serviceCode);

        return t;
    }

    public <T extends QueryCommonKeTopDTO> T sign(T t, String appSecret) {

        Object object = JSON.toJSON(t);
        String jsonString = JSON.toJSONString(object);
        Map<String, Object> map = JSON.parseObject(jsonString, TreeMap.class);

        map.forEach((k, v) -> {
            log.info("Key: " + k + "---" + "Value: " + v);
        });

        TreeMap<String, String> treeMap = new TreeMap<>();
        map.forEach((k, v) -> {
            if (null!=k && !"".equals(k) && !"appId".equals(k) && !"appSecret".equals(k) &&
                    null!=v && !(v instanceof Map) && !(v instanceof Iterable)) {
                treeMap.put(k, String.valueOf(v));
            }
        });

        StringBuilder stringBuilder = new StringBuilder();
        treeMap.forEach((k, v) -> {
            stringBuilder.append(k).append("=").append(v).append("&");
        });
        stringBuilder.append(appSecret);

        String md5String = DigestUtils.md5DigestAsHex(stringBuilder.toString().getBytes(StandardCharsets.UTF_8));
        String md5StringUpperCase = md5String.toUpperCase();

        t.setKey(md5StringUpperCase);

        String s = JSON.toJSONString(t);
        log.info("result json string: " + s);

        return t;
    }


    private <T extends ManipulationKeTopCommonDTO> T preHandle(T t, Integer parkId, String serviceCode) {
        t.setParkId(parkId);
        t.setReqId(UUID.randomUUID().toString());
        t.setTs(String.valueOf(System.currentTimeMillis()));
        t.setServiceCode(serviceCode);
        return t;
    }

    public <T extends ManipulationKeTopCommonDTO> T sign(T t, VehicleParkingInfoBO vehicleParkingInfoBO, String serviceCode) {
        Integer parkId = Integer.valueOf(vehicleParkingInfoBO.getParkId());
        Map<String, Object> map = BeanUtil.beanToMap(preHandle(t, parkId, serviceCode), false, true);

        map.forEach((k, v) -> {
            System.out.println("key: " + k + "---" + "value: " + v);
        });

        map.entrySet().removeIf(entry -> "".equals(entry.getValue()));

        System.out.println("----------------------");

        map.forEach((k, v) -> {
            System.out.println("key: " + k + "---" + "value: " + v);
        });

        t.setKey(SecureUtil.signParams(DigestAlgorithm.MD5, map, "&", "=", true, "&", vehicleParkingInfoBO.getAppSecret()).toUpperCase());
        t.setAppId(vehicleParkingInfoBO.getAppId());
        return t;
    }

}
